﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Documents;
using SSCAI.Model;
using SSCAI.Client.ViewModels;
using SSCAI.Common;
using SSCAI.DAL;
using System.Threading;
using System.Windows.Threading;
using SSCAI.Filter;
using System.IO;

namespace SSCAI.Client
{
    /// <summary>
    /// Interaction logic for ReleaseWindow.xaml
    /// </summary>
    public partial class ReleaseWindow : Window
    {
        private int timeSpan = 600;

        DispatcherTimer dispatcherTimer;
        DispatcherTimer countdownTimer;
        DispatcherTimer initDataTimer;

        MainWindowsViewModel vm = null;
        private bool updateState = false;
        private bool isAdded = false;
        private Countdown countdown = new Countdown();

        private List<bool> threadStates = new List<bool>() { false, false, false, false, false, false, false, false, false, false };

        private static string path = string.Empty;

        private static FilterModel filterModel = new FilterModel();

        public ReleaseWindow()
        {

            InitializeComponent();
            for (int i = 0; i <= 30; i++)
            {
                this.cmb012.Items.Add(i);
            }

            this.cmb012.SelectedIndex = 0;

            for (int i = 0; i <= 100; i++)
            {
                this.cmb0123.Items.Add(i);
            }
            this.cmb0123.SelectedIndex = 0;
            for (int i = 0; i <= 200; i++)
            {
                this.cmb01234.Items.Add(i);
            }

            this.cmb01234.SelectedIndex = 0;

            this.GetTimeSpan();
            this.btnGenerateDatas.IsEnabled = false;
            ThreadPool.QueueUserWorkItem(q => { this.CorrectCountdownTimer(); });

            ThreadPool.QueueUserWorkItem(q => { XmlHelper.UpdateAllData(30); this.updateState = true; });

            InicializeDispatcherTimer();

        }

        private void CorrectCountdownTimer()
        {
            DateTime lDate = DateTime.Now;
            countdown.TotalSeconds = timeSpan - (lDate.Minute % (this.timeSpan / 60)) * 60 - lDate.Second;
            this.isAdded = false;
        }

        private void GetTimeSpan()
        {
            var nowTime = DateTime.Now;
            if (nowTime.Hour >= 22 || nowTime.Hour <= 2)
            {
                this.timeSpan = 300;
            }
            else
            {
                this.timeSpan = 600;
            }

        }

        /// <summary>
        /// 初始化定时器
        /// </summary>
        void InicializeDispatcherTimer()
        {
            dispatcherTimer = new DispatcherTimer();
            dispatcherTimer.Tick += dispatcherTimer_Tick;
            dispatcherTimer.Interval = new TimeSpan(0, 0, 5);
            dispatcherTimer.Start();

            countdownTimer = new DispatcherTimer();
            countdownTimer.Tick += countdownTimer_Tick;
            countdownTimer.Interval = new TimeSpan(0, 0, 1);
            countdownTimer.Start();

            initDataTimer = new DispatcherTimer();
            initDataTimer.Tick += initDataTimer_Tick;
            initDataTimer.Interval = new TimeSpan(0, 0, 2);
            initDataTimer.Start();
        }

        private void initDataTimer_Tick(object sender, EventArgs e)
        {
            if (this.updateState)
            {

                vm = new MainWindowsViewModel();
                this.DataContext = vm;
                this.btnGenerateDatas.IsEnabled = true;
                initDataTimer.Stop();


            }
        }

        private void countdownTimer_Tick(object sender, EventArgs e)
        {
            this.GetTimeSpan();

            if (countdown.TotalSeconds == 0)
            {
                this.CorrectCountdownTimer();
            }

            txtCountdown.Text = string.Concat(countdown.Minutes.ToString("00"), " : ", countdown.Seconds.ToString("00"));
            countdown.TotalSeconds--;

        }

        void dispatcherTimer_Tick(object sender, EventArgs e)
        {
            if (this.updateState && !this.isAdded)
            {
                if (countdown.Minutes > (timeSpan / 60) - 2)
                {
                    XmlHelper.AddOneItem(out this.isAdded);

                    if (this.isAdded)
                    {
                        //To update data source. 
                        LotteryData.ClearInstance();
                        vm = new MainWindowsViewModel();
                        this.DataContext = vm;

                        //Display winner number
                        DisplayResult();
                    }
                }

            }
        }

        private void btnGenerateDatas_Click_1(object sender, RoutedEventArgs e)
        {
            this.btnGenerateDatas.IsEnabled = false;
            this.txtGeneratedData.Text = "正在生成数据......";

            FilterHelper.dataSource = new List<LotteryModel>();
            foreach (var i in LotteryData.GetInstance().Lotterys)
            {
                FilterHelper.dataSource.Add(i);
            }

            this.InitFilterModel();

            List<List<LotteryModel>> data = this.GetFiterData();

            this.CorrectCountdownTimer();

            ThreadPool.QueueUserWorkItem(q =>
            {
                while (true)
                {
                    Thread.Sleep(300);
                    if (this.IsFilterThreadsReady())
                    {
                        var allData = new List<LotteryModel>();
                        foreach (var d in data)
                        {
                            allData.AddRange(d);
                        }

                        string strCount = string.Format(DateTime.Now + " 共生成{0}注数据", allData.Count);

                        var generateDatas = string.Join(",", allData.Select(d => d.FourDNumber).OrderBy(n => n).ToArray());

                        this.txtGeneratedData.Dispatcher.Invoke(new Action(delegate() { this.txtGeneratedData.Text = string.Concat(strCount, generateDatas); }));
                        break;
                    }

                }
            });

            ThreadPool.QueueUserWorkItem(q =>
            {
                int counter = 0;
                while (true)
                {
                    Thread.Sleep(1000);

                    if (this.IsFilterThreadsReady())
                    {
                        this.ClearFilterThreadsState();
                        if (counter > 9)
                        {
                            this.btnGenerateDatas.Dispatcher.Invoke(new Action(delegate() { this.btnGenerateDatas.IsEnabled = true; }));
                            break;
                        }
                        var lastLottery = FilterHelper.dataSource.FirstOrDefault();
                        FilterHelper.dataSource.RemoveAt(0);

                        List<List<LotteryModel>> testData = this.GetFiterData();

                        counter++;
                    }


                }
            });
        }

        private List<List<LotteryModel>> GetFiterData()
        {

            FilterDelegate filters = this.GetFiters();

            List<List<LotteryModel>> data = new List<List<LotteryModel>>();

            ThreadPool.QueueUserWorkItem(q =>
            {
                List<LotteryModel> d1 = new List<LotteryModel>();
                for (int i = 9999; i > 8999; i--)
                {
                    LotteryModel d = new LotteryModel() { WinningNumber = i.ToString("00000"), IsValid = true };
                    filters(d);
                    if (d.IsValid)
                    {
                        d1.Add(d);
                    }
                }

                data.Add(d1);
                this.threadStates[0] = true;
            }, this.threadStates[0]);

            #region


            ThreadPool.QueueUserWorkItem(q =>
            {
                List<LotteryModel> d1 = new List<LotteryModel>();
                for (int i = 8999; i > 7999; i--)
                {
                    LotteryModel d = new LotteryModel() { WinningNumber = i.ToString("00000"), IsValid = true };
                    filters(d);
                    if (d.IsValid)
                    {
                        d1.Add(d);
                    }
                }
                data.Add(d1);
                this.threadStates[1] = true;
            }, this.threadStates[1]);


            ThreadPool.QueueUserWorkItem(q =>
            {
                List<LotteryModel> d1 = new List<LotteryModel>();
                for (int i = 7999; i > 6999; i--)
                {
                    LotteryModel d = new LotteryModel() { WinningNumber = i.ToString("00000"), IsValid = true };
                    filters(d);
                    if (d.IsValid)
                    {
                        d1.Add(d);
                    }
                }
                data.Add(d1);
                this.threadStates[2] = true;
            }, this.threadStates[2]);


            ThreadPool.QueueUserWorkItem(q =>
            {
                List<LotteryModel> d1 = new List<LotteryModel>();
                for (int i = 6999; i > 5999; i--)
                {
                    LotteryModel d = new LotteryModel() { WinningNumber = i.ToString("00000"), IsValid = true };
                    filters(d);
                    if (d.IsValid)
                    {
                        d1.Add(d);
                    }
                }
                data.Add(d1);
                this.threadStates[3] = true;
            }, this.threadStates[3]);


            ThreadPool.QueueUserWorkItem(q =>
            {
                List<LotteryModel> d1 = new List<LotteryModel>();
                for (int i = 5999; i > 4999; i--)
                {
                    LotteryModel d = new LotteryModel() { WinningNumber = i.ToString("00000"), IsValid = true };
                    filters(d);
                    if (d.IsValid)
                    {
                        d1.Add(d);
                    }
                }
                data.Add(d1);
                this.threadStates[4] = true;
            }, this.threadStates[4]);


            ThreadPool.QueueUserWorkItem(q =>
            {
                List<LotteryModel> d1 = new List<LotteryModel>();
                for (int i = 4999; i > 3999; i--)
                {
                    LotteryModel d = new LotteryModel() { WinningNumber = i.ToString("00000"), IsValid = true };
                    filters(d);
                    if (d.IsValid)
                    {
                        d1.Add(d);
                    }
                }
                data.Add(d1);
                this.threadStates[5] = true;
            }, this.threadStates[5]);

            ThreadPool.QueueUserWorkItem(q =>
            {
                List<LotteryModel> d1 = new List<LotteryModel>();
                for (int i = 3999; i > 2999; i--)
                {
                    LotteryModel d = new LotteryModel() { WinningNumber = i.ToString("00000"), IsValid = true };
                    filters(d);
                    if (d.IsValid)
                    {
                        d1.Add(d);
                    }
                }
                data.Add(d1);
                this.threadStates[6] = true;
            }, this.threadStates[6]);

            ThreadPool.QueueUserWorkItem(q =>
            {
                List<LotteryModel> d1 = new List<LotteryModel>();
                for (int i = 2999; i > 1999; i--)
                {
                    LotteryModel d = new LotteryModel() { WinningNumber = i.ToString("00000"), IsValid = true };
                    filters(d);
                    if (d.IsValid)
                    {
                        d1.Add(d);
                    }
                }
                data.Add(d1);
                this.threadStates[7] = true;
            }, this.threadStates[7]);

            ThreadPool.QueueUserWorkItem(q =>
            {
                List<LotteryModel> d1 = new List<LotteryModel>();
                for (int i = 1999; i > 999; i--)
                {
                    LotteryModel d = new LotteryModel() { WinningNumber = i.ToString("00000"), IsValid = true };
                    filters(d);
                    if (d.IsValid)
                    {
                        d1.Add(d);
                    }
                }
                data.Add(d1);
                this.threadStates[8] = true;
            }, this.threadStates[8]);

            ThreadPool.QueueUserWorkItem(q =>
            {
                List<LotteryModel> d1 = new List<LotteryModel>();
                for (int i = 999; i > -1; i--)
                {
                    LotteryModel d = new LotteryModel() { WinningNumber = i.ToString("00000"), IsValid = true };
                    filters(d);
                    if (d.IsValid)
                    {
                        d1.Add(d);
                    }
                }
                data.Add(d1);
                this.threadStates[9] = true;
            }, this.threadStates[9]);

            #endregion

            return data;
        }


        private bool IsFilterThreadsReady()
        {
            return this.threadStates.Where(t => t).Count() >= 10;
        }

        private void ClearFilterThreadsState()
        {
            this.threadStates = new List<bool>() { false, false, false, false, false, false, false, false, false, false };
        }

        private void btnExportDatas_Click_1(object sender, RoutedEventArgs e)
        {
            this.txtGeneratedData.IsEnabled = false;
            if (string.IsNullOrEmpty(this.txtGeneratedData.Text.Trim())) return;

            //SaveFileDialog dialog = new SaveFileDialog();
            //dialog.Title = "导出生成的投注数据";
            //var now = DateTime.Now;
            //dialog.FileName = "投注数据" + now.Year + now.Month + now.Day + now.Hour + now.Minute + now.Second;
            //dialog.Filter = "txt files (*.txt)|*.txt|All files (*.*)|*.*";
            //dialog.RestoreDirectory = true;
            //if (dialog.ShowDialog() == true)
            //{
            //    File.WriteAllText(dialog.FileName, this.txtGeneratedData.Text.Trim());
            //}

            string fileName = "ExportDatas.txt";
            string filePath = AppDomain.CurrentDomain.BaseDirectory;
            path = filePath + fileName;
            //创建并写入(将覆盖已有文件)
            if (!File.Exists(filePath + fileName))
            {
                using (FileStream stream = File.Create(path))
                { }
            }

            // Create a file to write to.
            using (StreamWriter sw = File.CreateText(path))
            {
                sw.WriteLine(this.txtGeneratedData.Text.Trim());
            }

            //MessageBox.Show("数据已导出", "提示", MessageBoxButton.OK, MessageBoxImage.Information);
            this.tbResult.Text = "在" + DateTime.Now + " 已导出数据，等待开奖...";

            this.txtGeneratedData.IsEnabled = true;
        }

        private void InitFilterModel()
        {

            filterModel.IsKillBaozi = Convert.ToBoolean(this.chbDengZhi.IsChecked);
            filterModel.IsKillDanMa = Convert.ToBoolean(this.chbDanMa.IsChecked);
            filterModel.IsKillHeZhi = Convert.ToBoolean(this.chbHeZhi.IsChecked);
            filterModel.IsKillKuaDuHe = Convert.ToBoolean(this.chbKuaDuHe.IsChecked);
            filterModel.IsKillSameSpan = Convert.ToBoolean(this.chbXiangTongKuaDu.IsChecked);
            filterModel.IsKillShunZiSpan = Convert.ToBoolean(this.chbShunZhiKuaDu.IsChecked);
            filterModel.IsKillLast200 = Convert.ToBoolean(this.chbQian200.IsChecked);
            //filterModel.IsKillLastIssue = Convert.ToBoolean(this.chbLatestIssue.IsChecked);
            filterModel.IsKillEveryWeiCool = Convert.ToBoolean(this.chbZuiLengHao.IsChecked);
            filterModel.IsKillShunZi = Convert.ToBoolean(this.chkShunzi.IsChecked);
            filterModel.IsKill0123 = Convert.ToBoolean(this.chk0123.IsChecked);
            filterModel.IsKill012 = Convert.ToBoolean(this.chk012.IsChecked);
            filterModel.IsKill0123 = Convert.ToBoolean(this.chk0123.IsChecked);
            filterModel.IsKill01234 = Convert.ToBoolean(this.chk01234.IsChecked);

            FilterHelper.kill012Count = Convert.ToInt16(this.cmb012.Text);
            FilterHelper.kill0123Count = Convert.ToInt16(this.cmb0123.Text);
            FilterHelper.kill01234Count = Convert.ToInt16(this.cmb01234.Text);
        }

        private FilterDelegate GetFiters()
        {

            FilterDelegate filters = new FilterDelegate(FilterHelper.FilterNothing);
            //杀豹子
            if (filterModel.IsKillBaozi) filters += new FilterDelegate(FilterHelper.KillLoepardData);

            //杀上期和值
            if (filterModel.IsKillHeZhi) filters += new FilterDelegate(FilterHelper.KillSumData);
            //杀跨度和
            if (filterModel.IsKillKuaDuHe) filters += new FilterDelegate(FilterHelper.KillKuaDuHe);

            //啥相同跨度
            if (filterModel.IsKillSameSpan) filters += new FilterDelegate(FilterHelper.KillXiangTongKuaDu);
            //杀顺子跨度
            if (filterModel.IsKillShunZiSpan) filters += new FilterDelegate(FilterHelper.KillShunZiKuaDu);
            //杀前200期
            if (filterModel.IsKillLast200) filters += new FilterDelegate(FilterHelper.KillQian200);

            //杀顺子:1234,2345...
            if (filterModel.IsKillShunZi) filters += new FilterDelegate(FilterHelper.KillShunZi);

            if (filterModel.IsKill012)
            {

                filters += new FilterDelegate(FilterHelper.Kill012);
            }
            if (filterModel.IsKill0123)
            {

                filters += new FilterDelegate(FilterHelper.Kill0123);
            }
            if (filterModel.IsKill01234)
            {

                filters += new FilterDelegate(FilterHelper.Kill01234);
            }

            //过滤胆码
            if (filterModel.IsKillDanMa)
            {
                var latestLottery = LotteryData.GetInstance().Lotterys.FirstOrDefault();
                FilterHelper.latestDanMaIndex = Math.Abs(latestLottery.GeWei - latestLottery.ShiWei);
                filters += new FilterDelegate(FilterHelper.DanMa);
            }

            // 过滤位最冷码
            if (filterModel.IsKillEveryWeiCool)
            {
                FilterHelper.maxWeiCoolCodes = FilterHelper.GetWeiCoolCodes();
                filters += new FilterDelegate(FilterHelper.KillEveryWeiZuiLengHao);
            }

            return filters;
        }

        private void DisplayResult()
        {
            if (!string.IsNullOrEmpty(path))
            {
                string savedDatas = "";
                StringBuilder sb = new StringBuilder();
                //读取文件
                using (StreamReader sr = File.OpenText(path))
                {
                    while ((savedDatas = sr.ReadLine()) != null)
                    {
                        sb.Append(savedDatas);
                    }
                }

                var latestData = LotteryData.GetInstance().Lotterys.First();
                string latestWinnerNumber = latestData.FourDNumber;
                string issue = latestData.Issue;

                if (sb.ToString().Contains(latestWinnerNumber))
                {
                    this.tbResult.Text = "第" + issue + "期开奖号码：" + latestWinnerNumber + "中奖";
                }
                else
                {
                    this.tbResult.Text = "第" + issue + "期开奖号码：" + latestWinnerNumber + "未中奖";
                }
            }

        }
    }

    //delegate void FilterDelegate(LotteryModel lottery);
}
